#include "button.h"

typedef struct
{
    uint8_t btn_pin_val;
    uint8_t btn_old_pin_val;
    uint8_t btn_repeat;
    uint32_t time;    /*长按*/
    uint32_t de_time; /*消抖*/
} button_t;

static button_event_cb_t button_event_cb = NULL;
static button_t buttons[BUTTONS_NUM] = {0};

void button_init(void)
{
    for (uint8_t id = 0; id < BUTTONS_NUM; ++id)
    {
        buttons[id].btn_pin_val = buttons[id].btn_old_pin_val = !BUTTON_PIN_VAL_PRESSED;
    }
}

void button_check(void)
{
    buttons[0].btn_pin_val = BUTTON_READ_PIN_VAL(0);
    buttons[1].btn_pin_val = BUTTON_READ_PIN_VAL(1);
    buttons[2].btn_pin_val = BUTTON_READ_PIN_VAL(2);

    for (uint8_t id = 0; id < BUTTONS_NUM; ++id)
    {

        /*消抖*/
        if (buttons[id].btn_pin_val != buttons[id].btn_old_pin_val)
        {
            buttons[id].de_time = HAL_GetTick();
        }
        else
        {
            uint32_t time = HAL_GetTick();
            uint32_t temp = 0;
            if (buttons[id].de_time > time) /*溢出了*/
            {
                temp = time + (0xFFFFFFFF - buttons[id].de_time);
            }
            else
            {
                temp = buttons[id].de_time - time;
            }

            if (temp < BUTTON_SHORT_PRESSED_TIME_MS)
            {
                buttons[id].btn_pin_val = buttons[id].btn_old_pin_val;
            }
        }

        /*按钮按下瞬间*/
        if (BUTTON_PIN_VAL_IS_PRESSED(buttons[id].btn_pin_val) &&
            !BUTTON_PIN_VAL_IS_PRESSED(buttons[id].btn_old_pin_val))
        {
            buttons[id].time = HAL_GetTick();
            if (button_set_event_cb)
                button_event_cb(id, EVENT_PRESSED);
        }
        /*判断按钮长按还是短按*/
        else if (BUTTON_PIN_VAL_IS_PRESSED(buttons[id].btn_pin_val) &&
                 BUTTON_PIN_VAL_IS_PRESSED(buttons[id].btn_old_pin_val))
        {
            uint32_t time = HAL_GetTick();
            uint32_t temp = 0;
            if (buttons[id].time > time) /*溢出了*/
            {
                temp = time + (0xFFFFFFFF - buttons[id].time);
            }
            else
            {
                temp = time - buttons[id].time;
            }

            if (!buttons[id].btn_repeat && (temp >= BUTTON_LONG_PRESSED_TIME_MS))
            {
                buttons[id].btn_repeat = 1;
                buttons[id].time = HAL_GetTick();
                if (button_set_event_cb)
                    button_event_cb(id, EVENT_LONG_PRESSED);
            }
            else if (temp >= BUTTON_REPEAT_TIME_MS)
            {
                buttons[id].time = HAL_GetTick();
                if (button_set_event_cb)
                    button_event_cb(id, EVENT_REPEAT);
            }
        }
        /*按钮释放瞬间*/
        else if (!BUTTON_PIN_VAL_IS_PRESSED(buttons[id].btn_pin_val) &&
                 BUTTON_PIN_VAL_IS_PRESSED(buttons[id].btn_old_pin_val))
        {
            if (button_set_event_cb)
                button_event_cb(id, EVENT_RELEASED);
        }
    }

    buttons[0].btn_old_pin_val = buttons[0].btn_pin_val;
    buttons[1].btn_old_pin_val = buttons[1].btn_pin_val;
    buttons[2].btn_old_pin_val = buttons[2].btn_pin_val;
}

void button_set_event_cb(button_event_cb_t cb)
{
    button_event_cb = cb;
}